using System;
using System.ComponentModel.Composition;
using System.Windows;
using System.Windows.Browser;

namespace OrbitOne.CRMLyncInfoDashboard.CRM
{
    [Export(typeof(IClientScript))]
    public class ClientScript : IClientScript
    {
        public Uri GetServerUrl()
        {
            var debug = Application.Current.Resources["Debug"];
            bool isDebug;
            if (debug != null && bool.TryParse(debug.ToString(), out isDebug) && isDebug)
            {
                return new Uri("https://crm2011.orbitone.com/OrbitOneCRM/");
            }

            const string defaultLocalServerUrl = ""; //"https://cn.crm4.dynamics.com/";

            var urlPath = HtmlPage.Document.DocumentUri.LocalPath;
            var url = HtmlPage.Document.DocumentUri.ToString();

            try
            {
                url = IsCrmOnline(url)
                ? GetCrmOnlineUrl()
                : GetCrmOnPremiseUrl(urlPath, url);
            }
            catch (Exception)
            {
                url = defaultLocalServerUrl;
                HtmlPage.Window.Invoke("alert", "Returning defaultLocalServerUrl");
            }

            return new Uri(url);
        }

        private static bool IsCrmOnline(string url)
        {
            return url.IndexOf(".crm.dynamics.com") > 0 | url.IndexOf(".crm4.dynamics.com") > 0 | url.IndexOf(".crm5.dynamics.com") > 0;
        }

        private string GetCrmOnlineUrl()
        {
            var url = GetCrmOnlineServerUrl();
            if (url.EndsWith("/"))
                url = url.Substring(0, url.Length - 1);
            return url;
        }

        private string GetCrmOnPremiseUrl(string urlPath, string url)
        {
            var orgName = GetCrmOnPremiseOrganizationName();
            url = url.Substring(0, url.IndexOf(urlPath) + 1);
            url += orgName + "/";
            return url;
        }

        private string GetCrmOnPremiseOrganizationName()
        {
            return (string)GetContext().Invoke("getOrgUniqueName");
        }

        private string GetCrmOnlineServerUrl()
        {
            return (string)GetContext().Invoke("getServerUrl");
        }

        private ScriptObject GetContext()
        {
            var xrmProperty = (ScriptObject)HtmlPage.Window.GetProperty("Xrm");
            if (xrmProperty == null)
            {
                try
                {
                    return GetGlobalContext();
                }
                catch (InvalidOperationException ioe)
                {
                    const string errorMessage = "Property \"Xrm\" is null and the Global Context is not available.";
                    HtmlPage.Window.Invoke("alert", errorMessage);
                }
            }

            var pageProperty = (ScriptObject)xrmProperty.GetProperty("Page");
            if (pageProperty == null)
            {
                const string errorMessage = "Property \"Xrm.Page\" is null";
                HtmlPage.Window.Invoke("alert", errorMessage);
            }

            var contextProperty = (ScriptObject)pageProperty.GetProperty("context");
            if (contextProperty == null)
            {
                const string errorMessage = "Property \"Xrm.Page.context\" is null";
                HtmlPage.Window.Invoke("alert", errorMessage);
            }
            return contextProperty;
        }

        private ScriptObject GetGlobalContext()
        {
            return (ScriptObject)HtmlPage.Window.Invoke("GetGlobalContext");
        }
    }
}
